#!/bin/sh
# THIS FILE IS RESERVED FOR THE EXCLUSIVE USE OF FREENAS CONFIG SYSTEM.
# Please edit /etc/rc.conf instead.

#-
# Copyright (c) 2010, 2011 iXsystems, Inc., All rights reserved.
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the following conditions
# are met:
# 1. Redistributions of source code must retain the above copyright
#    notice, this list of conditions and the following disclaimer.
# 2. Redistributions in binary form must reproduce the above copyright
#    notice, this list of conditions and the following disclaimer in the
#    documentation and/or other materials provided with the distribution.
#
# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
# ARE DISCLAIMED.  IN NO EVENT SHALL Jordan Hubbard OR CONTRIBUTORS BE LIABLE
# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
# SUCH DAMAGE.
#

. /etc/rc.freenas


http_ssl_enabled()
{
	local ssl=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "
		SELECT
			stg_guiprotocol
		FROM
			system_settings
		WHERE
			stg_guiprotocol = 'https'
		ORDER BY
			-id
		LIMIT 1
	")

	if [ -n "${ssl}" ]
	then
		return 0
	fi

	return 1
}

ftp_tls_enabled()
{
	local ssl=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "
		SELECT
			ftp_tls
		FROM
			services_ftp
		ORDER BY
			-id
		LIMIT 1
	")

	if [ "${ssl}" -gt "0" ]
	then
		return 0
	fi

	return 1
}

_interface_config()
{
	local failover_status="${1}"
	local failover_licensed=${2}
	local saved_ifs="${IFS}"
	local IFS=\|
	local interface_id interface dodhcp ipv4addr ipv4netmask doipv6auto ipv6addr ipv6netmask options
	local lagg_id laggproto lagg_physnic lagg_deviceoptions
	local vlan_vint vlan_pint vlan_tag vlan_pcp

	if [ `${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT COUNT(id) FROM network_interfaces"` = 0 ]; then
		IFS="${saved_ifs}"
		for interface in $(ifconfig -l)
		do
			if echo "${interface}"|egrep -q '^(bridge|epair|ipfw|lo)[0-9]+'
			then
				continue
			fi
			if echo "${interface}"|grep -q ':'
			then
				continue
			fi
			echo "ifconfig_${interface}=\"DHCP\""
		done
	fi

	local node
	local carp1_addr="169.254.10.20/32" carp2_addr="169.254.10.80/32"
	local carp1_skew carp2_skew
	local internal_ip internal_iface
	local configure_ifaces=1
	if ! is_freenas; then

		if [ "$(ha_mode)" = "MANUAL" ]; then
			if [ ${failover_licensed} -eq 1 ]; then
				configure_ifaces=0
				echo "# Unable to determine HA hardware and node, skipping interfaces configuration" | tee /dev/console
			fi
		else
			node=$(ha_node)
		fi

		if [ "${node}" = "A" ]; then
			carp1_skew="20"
			carp2_skew="80"
			internal_ip="169.254.10.1"
		elif [ "${node}" = "B" ]; then
			carp1_skew="80"
			carp2_skew="20"
			internal_ip="169.254.10.2"
		else
			echo "# Could not determine system node"
		fi

		if [ -n "${carp1_skew}" ]; then
			if [ "$(ha_hardware)" = "ECHOSTREAM" ]; then
				internal_iface=$(pciconf -lv | grep 'card=0xa01f8086 chip=0x10d38086' | awk -F@ '{print $1}')
                                if [ "${internal_iface}" = "" ]; then
                                        internal_iface=$(ifconfig -l | tr -s " " "\n" | grep "^em" | sort -r | head -1)
                                fi
			elif [ "$(ha_hardware)" = "SBB" ]; then
				internal_iface="ix0"
			elif [ "$(ha_hardware)" = "ECHOWARP" -o "$(ha_hardware)" = "PUMA" ]; then
				internal_iface="ntb0"
				if [ "${node}" = "A" ]; then
					ether="02:8c:97:2e:a5:01"
				else
					ether="02:8c:97:2e:a5:02"
				fi
			elif [ "$(ha_hardware)" = "ULTIMATE" ]; then
				internal_iface="igb1"
			elif [ "$(ha_hardware)" = "VMWARE" ]; then
				internal_iface="em1"
			fi
			local a=0
			if [ -n "${ether}" ]; then
				echo "ifconfig_${internal_iface}=\"ether ${ether}\""
				echo "ifconfig_${internal_iface}_alias${a}=\"inet ${internal_ip}/24 descr Interlink\""
				a=$(( $a + 1 ))
			else
				echo "ifconfig_${internal_iface}=\"inet ${internal_ip}/24 descr Interlink\""
			fi
			echo "ifconfig_${internal_iface}_alias${a}=\"inet vhid 10 advskew ${carp1_skew} alias ${carp1_addr}\""
			a=$(( $a + 1 ))
			echo "ifconfig_${internal_iface}_alias${a}=\"inet vhid 20 advskew ${carp2_skew} alias ${carp2_addr}\""
			a=$(( $a + 1 ))
		fi
	fi

	local IFS=\|
	# Note: ipv4/ipv6 are supposed in ip/masklen format.

	# Traverse the network interface table and generate rc.conf style
	# configuration.
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT id, int_interface, int_dhcp, int_ipv4address, int_ipv4address_b, int_v4netmaskbit, int_ipv6auto, int_ipv6address, int_v6netmaskbit, int_vip, int_vhid, int_pass, int_critical, int_group, int_options FROM network_interfaces ORDER BY id" | \
	while read interface_id interface dodhcp ipv4addr ipv4addr_b ipv4netmask doipv6auto ipv6addr ipv6netmask int_vip int_vhid int_pass critical group options; do
		if [ ${configure_ifaces} -ne 1 ]; then
			continue;
		fi
		if [ "$(ha_node)" = "B" ]; then
			ipv4addr=${ipv4addr_b}
		fi
		echo -n ifconfig_${interface}=\"
		if [ "${dodhcp}" = "1" ]; then
			echo -n "DHCP"
		elif [ -n "${ipv4addr}" ]; then
			echo -n "inet ${ipv4addr}/${ipv4netmask} "
		fi
		# Hook to support lagg(4) interfaces
		lagg_id=`${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT id FROM network_lagginterface WHERE lagg_interface_id = ${interface_id}"`
		if [ -n "${lagg_id}" ]; then
			laggproto=`${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT lagg_protocol FROM network_lagginterface WHERE lagg_interface_id = ${interface_id}"`
			echo -n " laggproto ${laggproto}"
			${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT lagg_physnic FROM network_lagginterfacemembers WHERE lagg_interfacegroup_id=${lagg_id} ORDER BY lagg_ordernum" | \
			while read lagg_physnic; do
				echo -n " laggport ${lagg_physnic}"
			done
		fi
		if [ -n "${options}" ]; then
			echo -n " ${options}"
		fi
		echo \"

		if [ "${int_vip}" != "" ]; then
			if [ -n "${int_pass}" ]; then
				int_passopt=" pass ${int_pass}"
			else
				int_passopt=""
			fi
			if [ "${failover_status}" = "MASTER" ]; then
				carp1_skew="1"
			fi
			echo -n "ifconfig_${interface}_alias0=\"inet vhid ${int_vhid} advskew ${carp1_skew}${int_passopt} alias ${int_vip}/32"
			if [ -n "${critical}" ]; then
				echo -n " descr CriticalGroup${group}"
			fi
			echo \"
			eval counter_${interface}=1

		fi

		local aliases has_ipv6
		aliases=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT id, alias_vip, alias_v4address, alias_v4address_b, alias_v4netmaskbit, alias_v6address, alias_v6address_b, alias_v6netmaskbit FROM network_alias WHERE alias_interface_id = ${interface_id} ORDER BY id" | \
		while read alias_id v4vip v4addr v4addr_b v4netmask v6addr v6addr_b v6netmask; do
			eval counter=\${counter_${interface}:-0}
			if [ "$(ha_node)" = "B" ]; then
				v4addr=${v4addr_b}
				v6addr=${v6addr_b}
			fi
			if [ -n "${int_vhid}" -a -n "${v4vip}" ]; then
				echo "ifconfig_${interface}_alias${counter}=\"inet vhid ${int_vhid} advskew ${carp1_skew}${int_passopt} alias ${v4vip}/32\""
				counter=$((counter+1))
			fi
			if [ -n "${v4addr}" ]; then
				echo "ifconfig_${interface}_alias${counter}=\"inet ${v4addr}/${v4netmask}\""
				counter=$((counter+1))
			fi
			if [ -n "${v6addr}" ]; then
				echo "ifconfig_${interface}_alias${counter}=\"inet6 ${v6addr}/${v6netmask}\""
				counter=$((counter+1))
			fi
			eval "counter_${interface}=\${counter}"
		done)
		echo ${aliases}
		has_ipv6=$(echo ${aliases}|grep -c inet6)

		if [ "$doipv6auto" = "1" ]; then
			echo ifconfig_${interface}_ipv6=\"inet6 accept_rtadv auto_linklocal\"
                        echo rtsold_enable=\"YES\"
		else
			if [ -n "${ipv6addr}" ]; then
				echo ifconfig_${interface}_ipv6=\"inet6 ${ipv6addr}/${ipv6netmask} auto_linklocal\"
                        elif [ ${has_ipv6} -gt 0 ]; then
                                echo ifconfig_${interface}_ipv6=\"inet6 auto_linklocal\"
                        fi
		fi
		if [ -n "${lagg_id}" ]; then
			cloned_interfaces="${cloned_interfaces} ${interface}"
			echo "cloned_interfaces=\"${cloned_interfaces}\""
		fi
	done


	#
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT lagg_physnic, lagg_deviceoptions, lagg_interfacegroup_id FROM network_lagginterfacemembers ORDER BY lagg_ordernum" | \
	while read lagg_physnic lagg_deviceoptions lagg_gid; do
		lagg_intoptions=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT int_options FROM network_interfaces INNER JOIN network_lagginterface ON network_interfaces.id=network_lagginterface.lagg_interface_id WHERE network_lagginterface.id=${lagg_gid}")
		echo "ifconfig_${lagg_physnic}=\"${lagg_intoptions} ${lagg_deviceoptions}\""
	done

	# Hook to support vlan interfaces
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT DISTINCT vlan_pint from network_vlan" | \
	while read vlan_pint; do
		echo -n vlans_${vlan_pint}=\"
		${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT vlan_vint from network_vlan WHERE vlan_pint = \"${vlan_pint}\"" | xargs echo -n
		echo \"
	done

	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT vlan_vint, vlan_tag, vlan_pcp from network_vlan" | \
	while read vlan_vint vlan_tag vlan_pcp; do
		echo -n create_args_${vlan_vint}=\"vlan\ ${vlan_tag}
		if [ -n "${vlan_pcp}" ]; then
			echo -n " vlanpcp ${vlan_pcp}"
		fi
		echo \"
	done
}

_host_config()
{
	local IFS=\|
	local hostname domainname nameserver1 nameserver2 nameserver3 ipv4gateway ipv6gateway netwait_enabled netwait_ip hostname_field
	if [ "$(ha_node)" = "B" ]; then
		hostname_field="gc_hostname_b"
	else
		hostname_field="gc_hostname"
	fi
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT ${hostname_field}, gc_domain, gc_nameserver1, gc_nameserver2, gc_nameserver3, gc_ipv4gateway, gc_ipv6gateway, gc_netwait_enabled, gc_netwait_ip FROM network_globalconfiguration ORDER BY -id LIMIT 1" | \
	while read -r hostname domainname nameserver1 nameserver2 nameserver3 ipv4gateway ipv6gateway netwait_enabled netwait_ip; do
		echo hostname=\"${hostname}.${domainname}\"
		if [ -n "${ipv4gateway}" ]; then
			echo defaultrouter=\"${ipv4gateway}\"
		fi
		if [ -n "${ipv6gateway}" ]; then
			echo ipv6_defaultrouter=\"${ipv6gateway}\"
		fi

		if [ "${netwait_enabled}" = 1 ]; then
			echo netwait_enable=\"YES\"
			if [ -z "${netwait_ip}" ]; then
				if [ -n "${ipv4gateway}" ]; then
					netwait_ip=${ipv4gateway}
				elif [ -n "${ipv6gateway}" ]; then
					netwait_ip=${ipv6gateway}
				fi
			fi
			echo netwait_ip=\"${netwait_ip}\"
		fi
	done
}

# _bool_config /variable/ /table/ /field/
_bool_config()
{
	local IFS=\|
	local boolvalue value key
	if [ -n "$4" ]; then
		key="$4"
	else
		key="id"
	fi
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT $3 FROM $2 ORDER BY ${key} DESC LIMIT 1" | \
	while read boolvalue; do
		if [ "${boolvalue}" = "1" ]; then
			value="YES"
		else
			value="NO"
		fi
		echo $1=\"${value}\"
	done
}

# _count_config /variable/ /table/ /field/ /where/
_count_config()
{
	local count value
	count=`${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT COUNT($3) FROM $2 WHERE $3$4"`
	if [ "${count}" -gt "0" ]; then
		value="YES"
	else
		value="NO"
	fi
	echo $1=\"${value}\"
}

# _bool_svcconfig /variable/ /service_name/
_bool_svcconfig()
{
	local IFS=\|
	local boolvalue value
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT srv_enable FROM services_services WHERE srv_service='$2' ORDER BY id DESC LIMIT 1" | \
	while read boolvalue; do
		if [ "${boolvalue}" = "1" ]; then
			value="YES"
		else
			value="NO"
		fi
		echo $1=\"${value}\"
	done
}

# Grab static route configuration
_staticroute_config()
{
	local IFS=\|
	local id destination gateway interface static_routes

	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT id, sr_destination, sr_gateway FROM network_staticroute;" | \
	while read -r id destination gateway; do
		echo route_freenas${id}=\"-net ${destination} ${gateway}\"
	done
	static_routes=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT id FROM network_staticroute" | sed -e s/^/freenas/g | xargs echo)
	if [ -n "${static_routes:-}" ]; then
		echo static_routes=\"$static_routes\"
	fi
}

_nis_config() {
	local IFS=\|
	local nisdomain nisservers nissecure nismanycast

	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nis_domain, nis_servers, nis_secure_mode, nis_manycast FROM directoryservice_nis;" | \
	while read -r nisdomain nisservers nissecure nismanycast; do
		local nisflags="-S ${nisdomain}"

		echo "nisdomainname=\"${nisdomain}\""
		echo "nis_client_enable=\"YES\""

		if [ -n "${nisservers}" ]; then
			nisflags="${nisflags},${nisservers}"
		fi
		if [ "${nissecure}" = "1" ]; then
			nisflags="${nisflags} -s"
		fi
		if [ "${nismanycast}" = "1" ]; then
			nisflags="${nisflags} -m"
		fi

		echo "nis_client_flags=\"${nisflags}\""
	done
}

_nut_config() {
	local IFS=\|
	local boolvalue ups_identifier ups_mode ups_remotehost ups_remoteport
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT srv_enable FROM services_services WHERE srv_service='ups' AND srv_enable = 1 LIMIT 1" | \
	while read boolvalue; do
		${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT ups_mode, ups_remotehost, ups_remoteport, ups_identifier FROM services_ups" | \
		while read -r ups_mode ups_remotehost ups_remoteport ups_identifier; do
			if [ "${ups_mode}" = "master" ]; then
				echo "nut_enable=\"YES\""
				echo "nut_upsshut=\"NO\""
				echo "nut_upslog_ups=\"${ups_identifier}\""
			else
				echo "nut_upslog_ups=\"${ups_identifier}@${ups_remotehost}:${ups_remoteport}\""
			fi
			echo "nut_upslog_enable=\"YES\""
			echo "nut_upsmon_enable=\"YES\""
		done
	done
}

_s3_config()
{
	local IFS=\|
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "
		SELECT
			srv_enable as s3_enable,
			s3_bindip,
			s3_bindport,
			s3_access_key,
			s3_secret_key,
			s3_browser,
			s3_mode,
			s3_disks
		FROM
			services_s3
		LEFT OUTER JOIN
			services_services
		ON
			(srv_service = 's3' AND srv_enable = '1')
		ORDER BY
			-services_s3.id
		LIMIT 1
	" |\
	while read s3_enable s3_bindip s3_bindport s3_access_key \
		s3_secret_key s3_browser s3_mode s3_disks; do
		s3_access_key=$(echo "$s3_access_key" | sed 's/"/"'"'"'"'"'"'"''/g')
		s3_secret_key=$(echo "$s3_secret_key" | sed 's/"/"'"'"'"'"'"'"''/g')
		cat <<-__MINIO__
			minio_enable="YES"
			minio_disks="${s3_disks}"
			minio_address="${s3_bindip}:${s3_bindport}"
			minio_env="\\
			MINIO_ACCESS_KEY=${s3_access_key} \\
			MINIO_SECRET_KEY=${s3_secret_key} \\
			"
__MINIO__
		if [ "${s3_browser}" = "0" ]; then
			echo MINIO_BROWSER=off
		fi
	done
}

_snmp_config()
{
	echo "snmpd_conffile=\"/etc/local/snmpd.conf\""

	local snmpd_loglevel=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT snmp_loglevel FROM services_snmp ORDER BY -id LIMIT 1")
	echo "snmpd_flags=\"-LS${snmpd_loglevel}d\""
}

_ssl_config()
{
	local ssl_list

	if http_ssl_enabled
	then
		ssl_list="${ssl_list} nginx"
	fi

	if ftp_tls_enabled
	then
		ssl_list="${ssl_list} proftpd"
	fi

	ssl_list=$(echo ${ssl_list}|xargs)
	echo "ixssl_list=\"${ssl_list}\""
}

_sssd_config()
{
	sssd_enable="NO"
	if dirsrv_enabled ldap ; then
		sssd_enable="YES"
	fi
	if dirsrv_enabled activedirectory; then
		local ad_unix=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "
			SELECT
				ad_unix_extensions
			FROM
				directoryservice_activedirectory
			ORDER BY
				-id
			LIMIT 1
		")
		if [ "${ad_unix}" = "1" ]; then
			sssd_enable="YES"
		fi
	fi
	echo "sssd_enable=\"${sssd_enable}\""
}

_gen_conf()
{
	local failover_status="" failover_licensed=0
	if ! is_freenas; then
		if [ "$(ulimit -n 1000; /usr/local/bin/python /usr/local/www/freenasUI/failover/licensed.py 2> /dev/null)" = "True" ]; then
			failover_licensed=1
		fi
		failover_status="$(ulimit -n 1000; /usr/local/bin/python /usr/local/www/freenasUI/middleware/notifier.py failover_status 2> /dev/null)"
	fi

	## First, import network interface configuration.
	_interface_config ${failover_status} ${failover_licensed}
	_host_config
	_staticroute_config

	## Daemons
	_bool_svcconfig netatalk_enable afp
	_bool_svcconfig proftpd_enable ftp
	_bool_svcconfig nfs_server_enable nfs
	_bool_svcconfig rpc_lockd_enable nfs
	_bool_svcconfig rpc_statd_enable nfs
	_bool_svcconfig mountd_enable nfs
	_bool_svcconfig nfsd_enable nfs
	_bool_svcconfig rpcbind_enable nfs
	_bool_svcconfig rsyncd_enable rsync
	_bool_svcconfig snmpd_enable snmp
	_bool_svcconfig snmp_agent_enable snmp
	_bool_svcconfig openssh_enable ssh
	_bool_svcconfig inetd_enable tftp
	_bool_svcconfig inadyn_enable dynamicdns
	_bool_svcconfig smartd_daemon_enable smartd
	_bool_svcconfig ladvd_enable lldp
	_bool_svcconfig ctld_enable iscsitarget
	_bool_svcconfig apache24_enable webdav
	_bool_svcconfig netdata_enable netdata


	_bool_svcconfig samba_server_enable cifs
	if ! dirsrv_enabled domaincontroller ; then
		_bool_svcconfig smbd_enable cifs
		_bool_svcconfig nmbd_enable cifs
		_bool_svcconfig winbindd_enable cifs
	fi

	if dirsrv_enabled nis; then
		_nis_config
	fi

	_snmp_config

	_sssd_config
	_nut_config

	# Workaround: we don't enable ZFS by default but still want /etc/zfs/exports
	# be exist for mountd(8)
	if [ ! -r /etc/zfs/exports ]; then
		touch /etc/zfs/exports
	fi

	if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT srv_enable from services_services WHERE srv_service = 'nfs'")" = 1 ]; then

		if ! is_freenas; then
			echo "vaaiserver_enable=\"YES\""
		fi

		# NFS service is enabled
		if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_v4 FROM services_nfs")" = 1 ]; then
			# NFSv4 is enabled
			echo "nfsv4_server_enable=\"YES\""
			if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_v4_v3owner FROM services_nfs")" = 1 ]; then
				# NFSv3 ownership style for NFSv4 is selected.  Note this is mutually incompatible
				# with the >16 group support.
				echo "nfsuserd_enable=\"NO\""
				sysctl vfs.nfsd.enable_stringtouid=1 > /dev/null
				sysctl vfs.nfs.enable_uidtostring=1 > /dev/null
			else
				echo "nfsuserd_enable=\"YES\""
				sysctl vfs.nfsd.enable_stringtouid=0 > /dev/null
				sysctl vfs.nfs.enable_uidtostring=0 > /dev/null
				if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_16 FROM services_nfs")" = 1 ]; then
					# >16 group support
					echo "nfsuserd_flags=\"-manage-gids\""
				fi
			fi
		else
			# NFSv4 is not enabled
			if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_16 FROM services_nfs")" = 1 ]; then
				# we use nfsuserd to support more than 16 groups
				echo "nfsuserd_enable=\"YES\""
				echo "nfsuserd_flags=\"-manage-gids\""
			fi
			echo "nfsv4_server_enable=\"NO\""
		fi

		if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_v4_krb FROM services_nfs")" = 1 ]; then
			# NFSv4 is kerberos only
			echo "gssd_enable=\"YES\""
		else
			if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT COUNT() FROM directoryservice_kerberoskeytab")" = 0 ]; then
				# There are no keytabs in the database
				echo "gssd_enable=\"NO\""
			else
				# Keytabs found.  Turn on kerberos support for NFS
				# Note that in this case kerberos won't be *required* for NFS
				# but it will work.
				echo "gssd_enable=\"YES\""
			fi
		fi
	fi

	if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT COUNT() FROM storage_volume")" != 0 ]; then
		echo "zfs_enable=\"YES\""
	fi

	_count_config powerd_enable system_advanced adv_powerdaemon =1
	if ! is_freenas; then
		if [ ${failover_licensed} -eq 1 ]; then
			echo "failover_enable=\"YES\""
			echo "pf_enable=\"YES\""
		else
			echo "failover_enable=\"NO\""
		fi
		if [ "${failover_status}" != "BACKUP" ]; then
			echo "collectd_enable=\"YES\""
		fi

		echo "middlewared_overlay_dirs=\"/usr/local/lib/middlewared_truenas\""
	else
		echo "collectd_enable=\"YES\""
		echo "failover_enable=\"NO\""
	fi


	if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT adv_consolescreensaver FROM system_advanced ORDER BY -id LIMIT 1")" = 1 ]; then
		echo "saver=\"daemon\""
	fi

        local nonroot mountdflags statdflags lockdflags ip nfsips mountdport statdport lockdport
        
        if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_mountd_log FROM services_nfs ORDER BY -id LIMIT 1")" = 1 ]; then
                mountdflags="-l -rS"
        else
                mountdflags="-rS"
        fi
                
        if [ "$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_statd_lockd_log FROM services_nfs ORDER BY -id LIMIT 1")" = 1 ]; then
                statdflags=" -d"
                lockdflags=" -d 10"
        else
                statdflags=" "
                lockdflags=" "
        fi

	# Make sure IPs bind to NFS are in the interfaces (exist!) #16044
	nfsips=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_bindip FROM services_nfs ORDER BY -id LIMIT 1" | tr "," \\n | \
	while read -r ip; do
		if [ -n "${ip}" ] && ! /sbin/ifconfig -a inet|grep " ${ip} "; then
			echo "NOTFOUND"
			break
		fi
	done)

	if [ "x${nfsips}" = "xNOTFOUND" ]; then
		nfsips=""
		touch /tmp/.nfsbindip_notfound
	else
		rm -f /tmp/.nfsbindip_notfound
		nfsips=$(${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_bindip FROM services_nfs ORDER BY -id LIMIT 1" | tr "," \\n | \
		while read -r ip; do
			if [ -n "${ip}" ]; then
				echo -n "-h ${ip} "
			fi
		done)
	fi

	# set NFS server options
	local IFS=\|
	local numservers nfsudp
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_servers, nfs_srv_udp FROM services_nfs ORDER BY id DESC LIMIT 1" | \
	while read numservers nfsudp; do
		if [ "${nfsudp}" = 0 ]; then
			echo "nfs_server_flags=\"-t -n ${numservers} ${nfsips}\""
		else
			echo "nfs_server_flags=\"-t -u -n ${numservers} ${nfsips}\""
		fi
	done

	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT nfs_srv_allow_nonroot, nfs_srv_mountd_port, nfs_srv_rpcstatd_port, nfs_srv_rpclockd_port FROM services_nfs ORDER BY -id LIMIT 1" | \
	while read -r nonroot mountdport statdport lockdport; do
		if [ "${nonroot}" = 1 ]; then
			mountdflags="${mountdflags}n"
		fi
		if [ -n "${mountdport}" ]; then
			mountdflags="${mountdflags} -p ${mountdport}"
		fi
		if [ -n "${statdport}" ]; then
			statdport="${statdflags} -p ${statdport}"
		fi
		if [ -n "${lockdport}" ]; then
			lockdport="${lockdflags} -p ${lockdport}"
		fi
		if [ -n "${nfsips}" ]; then
			mountdflags="${mountdflags} ${nfsips}"
			echo "rpcbind_flags=\"${nfsips}\""
		fi
		echo "rpc_statd_flags=\"${nfsips}${statdport}\""
		echo "rpc_lockd_flags=\"${lockdport}\""
		echo "mountd_flags=\"${mountdflags}\""
	done

	local smartdint
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT smart_interval FROM services_smart ORDER BY id DESC LIMIT 1" | \
	while read smartdint; do
		inter=$(echo "${smartdint}*60"|/usr/bin/bc)
		echo "smartd_daemon_flags=\"-i ${inter}\""
	done

	_s3_config
	_ssl_config

	local kbdmap
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT stg_kbdmap FROM system_settings ORDER BY -id LIMIT 1" | \
	while read -r kbdmap; do
		if [ -n "${kbdmap}" ]; then
			echo "keymap=\"${kbdmap}\""
		fi
	done

	if [ ${failover_licensed} -ne 1 ]
	then
		echo "geli_devices=\"`${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT encrypted_provider FROM storage_encrypteddisk e JOIN storage_volume v ON e.encrypted_volume_id = v.id WHERE v.vol_encrypt=1;" | \
			tr \\\n \  `\""
		${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT e.encrypted_provider,v.vol_encryptkey FROM storage_encrypteddisk e JOIN storage_volume v ON e.encrypted_volume_id = v.id WHERE v.vol_encrypt=1;" | \
		while read -r provider key; do
			_provider=`echo ${provider}|tr '/-' '_'`
			echo "geli_${_provider}_flags=\"-p -k /data/geli/${key}.key\""
		done
	fi

	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT lldp_intdesc, lldp_country, lldp_location FROM services_lldp ORDER BY -id LIMIT 1" | \
	while read -r lldp_intdesc lldp_country lldp_location; do
		echo -n "ladvd_flags=\"-a"
		[ "${lldp_intdesc}" = 1 ] && echo -n " -z"
		[ -n "${lldp_country}" ] && echo -n " -c ${lldp_country}"
		[ -n "${lldp_location}" ] && echo -n " -l \\\"${lldp_location}\\\""
		echo "\""
	done

	if is_freenas; then
		echo "ataidle_enable=\"YES\""
		# Needed to use pbi repositories
		echo "pbid_enable=\"YES\""
		# Bug #7337 -- blacklist AMD systems for now
		if /sbin/sysctl hw.model | grep -q AMD; then
			echo "watchdogd_enable=\"NO\""
		else
			local product
			product=`/usr/local/sbin/dmidecode -s baseboard-product-name | /usr/bin/head -n 1`
			if [ "${product}" = "X9DR3-F" -o "${product}" = "X9DR3-LN4F+" ] ; then
				echo "watchdogd_enable=\"NO\""
			elif [ "${product}" = "C2750D4I" -o "${product}" = "C2550D4I" ] && [ "$(/usr/local/bin/ipmitool mc info 2> /dev/null | grep ^Firmware | cut -d . -f 2)" -lt 30 ] ; then
				echo "watchdogd_flags=\"-t 30 --softtimeout --softtimeout-action log,printf --pretimeout 15 --pretimeout-action log,printf -e 'sleep 1' -w -T 3\""
				echo "watchdogd_enable=\"YES\""
			else
				echo "watchdogd_flags=\"--pretimeout 5 --pretimeout-action log,printf\""
				echo "watchdogd_enable=\"YES\""
			fi
		fi
	else
		echo "ataidle_enable=\"NO\""
		echo "watchdogd_enable=\"NO\""
	fi

	local tun_var tun_value
	${FREENAS_SQLITE_CMD} ${FREENAS_CONFIG} "SELECT tun_var, tun_value FROM system_tunable WHERE tun_enabled = 1 AND tun_type = 'rc' ORDER BY id" | \
	while read -r tun_var tun_value; do
		echo "${tun_var}=\"${tun_value}\""
	done

	# FreeNAS 9.10 uses zfsd
	echo "zfsd_enable=\"YES\""

	if $(/usr/local/bin/vmware-checkvm > /dev/null); then
		echo "vmware_guestd_enable=\"YES\""
	else
		echo "vmware_guestd_enable=\"NO\""
	fi
}

# Regenerate stale caches of rc.conf data.  We run multiple time
# as part of the boot process, and this helps.  It also provides
# a useful file to look at for debugging.
#
# Previously mtime was being used to invalidate the cache
# However this solution could not deal with backward date changes
_NEWSUM=$(md5 -q ${FREENAS_CONFIG})
_OLDSUM=$(cat ${FREENAS_CONFIG_MD5} 2> /dev/null)
if [ ! "${_NEWSUM}" = "${_OLDSUM}" -a ! -f "${NEED_UPDATE_SENTINEL}" ]; then
	# There are some circunstances which make concurrent runs of
	# this script possible, e.g. devd carp script
	# To make it atomic generate to a tmp file first then move it.
	# See #23047
	tmpfile=$(/usr/bin/mktemp /var/tmp/rc.conf.tmp.XXXXXXXXX)
	_gen_conf > ${tmpfile}
	mv ${tmpfile} ${FREENAS_RC}
	rm -f /var/tmp/rc.conf.tmp.*
	echo ${_NEWSUM} > ${FREENAS_CONFIG_MD5}
fi

# Force LANG in the rc subsystem.
# This will allow python scripts (mostly) to get correct encoding
# while generating config files. See #24973
export LANG=en_US.UTF-8
if [ -f ${FREENAS_RC} ]; then
	. ${FREENAS_RC}
fi
